package com.gogant.spider.util;

public class StringUtils {

	/**
	 * 将一个对象根据条件组转换：decode(条件,值1,返回值1,值2,返回值2,...值n,返回值n,缺省值)
	 * 
	 * @param o
	 * @param values
	 * @return
	 */
	public static String decode(Object o, Object... values) {
		Object value = null;
		if (values == null || values.length == 0) {
			value = o;
		} else {
			int n = values.length;
			if (values.length % 2 == 0) {
				n -= 2;
			} else {
				n -= 3;
				value = values[values.length - 1];
			}
			for (int i = 0; i <= n; i += 2) {
				if ((o == null && values[i] == null) || (o != null && o.equals(values[i]))) {
					value = values[i + 1];
					break;
				}
			}
		}
		return value == null ? null : value.toString();
	}

	private static int[] findBlock(char[] src, int srcFrom, char[] exp, int expFrom, boolean skipFirst) {
		int i = srcFrom, j = expFrom, n = 0;
		for (; j < exp.length; j++) {
			char c = exp[j];
			if (c == '%') {
				return new int[] { i, j + 1 };
			} else if (c == '_') {
				if (i >= src.length) {
					return null;
				} else {
					n++;
					i++;
					continue;
				}
			}
			if (c == '\\' && j + 1 < exp.length) {
				char t = exp[j + 1];
				if (t == '_' || t == '%') {
					c = t;
					j++;
				}
			}
			if (i >= src.length) {
				return null;
			} else if (src[i] == c) {
				n++;
				i++;
			} else if (skipFirst) {
				while (true) {
					if (++i >= src.length) {
						return null;
					}
					if (n > 0) {
						n = 0;
						j = expFrom - 1;
						i = ++srcFrom;
						break;
					} else if (src[i] == c) {
						n++;
						i++;
						break;
					}
				}
			} else {
				return null;
			}
		}
		return new int[] { i, j };
	}

	/**
	 * 字符串like匹配，与SQL中的like一样，转义字符为‘\’，如果转义字符后面不跟‘_’或者‘%’，则继续作为字符‘\’进行处理
	 * 
	 * @param str
	 * @param expression
	 * @return
	 */
	public static boolean isLike(String str, String expression) {
		if (str == null) {
			return expression == null;
		} else if (str.length() == 0) {
			return expression != null && expression.length() == 0;
		} else if (expression == null || expression.length() == 0) {
			return false;
		}
		char[] exps = expression.toCharArray();
		char[] src = str.toCharArray();
		for (int i = 0, j = 0, k = 0;;) {
			int[] idx = findBlock(src, i, exps, j, k == 1);
			if (idx == null) {
				return false;
			} else {
				j = idx[1];
				i = idx[0];
				if (j == exps.length) {
					return i == src.length || exps[j - 1] == '%';
				}
				k = 1;
			}
		}
	}
}
